/*  
 * 极简AES加解密算法 （密钥字典加解密）
 * Version 1.1 Copyright (C) Qiepro kidming 2022-5-26.  
 * 
 * 密钥字符为不重复的任意字符
 * 加密后的数据会根据字典长度变化。字典长度最小为2，最大为128，最优为16，例：0123456789abcdef
 * 字典内容请不要以顺序排列，相当于密钥。如果要完全保证数据安全，字典数据不要存程序内部（可由输入数据传入参数）
 */
const default_key = '0123456789abcdefghijklmnopqrstuvwxyz';
module.exports = {
	Decrypt: function(crypt_str,aes_key = null){
		aes_key = this.StrUnique(aes_key == null ? default_key : String(aes_key));
		crypt_str = String(crypt_str);
		if(aes_key.length < 2) return false;
		let max = 255; // 最大值
		let alen; // 加密过后单字符长度
		for (alen = 0; max > 0; alen++) max = Math.floor(max / aes_key.length); //计算单字符加密后长度
		let result = [];
		let code = 0;
		for(let i=crypt_str.length-1;i>=0;i--){
			code += aes_key.indexOf(crypt_str.charAt(i))*(aes_key.length**((alen-1)-(i % alen)))
			if(i % alen === 0){
				result.unshift(String.fromCharCode(code+((crypt_str.length/alen)%13)))
				code = 0;
			}
		}
		return unescape(result.join(''));
	},
	Encrypt: function(source_str,aes_key = null){
		aes_key = this.StrUnique(aes_key == null ? default_key : String(aes_key));
		source_str = escape(source_str);
		if(aes_key.length < 2) return false;
		let max = 255; // 最大值
		let alen; // 加密过后单字符长度
		for (alen = 0; max > 0; alen++) max = Math.floor(max / aes_key.length); //计算单字符加密后长度
		let result = '';
		for (let i = 0; i < source_str.length; i++) {
			let num = source_str.charCodeAt(i)-(source_str.length % 13) // 字符编码，用fromCharCode解码；
			let arr = new Array(alen); // 单字符转换过后的数组
			for (let si = alen; si > 0; si--) {
				arr[si - 1] = aes_key.charAt(num % aes_key.length)
				num = Math.floor(num / aes_key.length);
			}
			result += arr.join('');
		}
		return result;
	},
	StrUnique(str){
		let temp = str.split('');
		const resArr = Array.from(new Set(temp));
		return resArr.join('');
	}
}
